package com.kingsailor.gunsmith.freemarker;

import com.kingsailor.gunsmith.security.UserAccessControlService;
import freemarker.template.SimpleScalar;
import freemarker.template.TemplateModelException;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.beans.factory.annotation.Value;
import org.springframework.context.ApplicationContext;
import org.springframework.context.annotation.Configuration;
import org.springframework.core.env.Environment;

import javax.annotation.PostConstruct;
import java.util.ArrayList;
import java.util.HashMap;

/**
 * @author xulixin
 */
@Configuration
public class RapidFreeMarkerConfig {

    private static final Logger log = LoggerFactory.getLogger(RapidFreeMarkerConfig.class);

    private final ApplicationContext applicationContext;

    protected final freemarker.template.Configuration configuration;

    private final FreeMarkerSharedVariableRegisterAware[] sharedVariableRegisters;

    @Value("${server.servlet.context-path:}")
    private String ctxPath;

    public RapidFreeMarkerConfig(ApplicationContext applicationContext,
                                 freemarker.template.Configuration configuration,
                                 FreeMarkerSharedVariableRegisterAware[] sharedVariableRegisters) {

        this.applicationContext = applicationContext;
        this.configuration = configuration;
        this.sharedVariableRegisters = sharedVariableRegisters;
    }

    /**
     * 添加自定义标签
     */
    @PostConstruct
    public void setSharedVariable() {
        Environment env = this.applicationContext.getEnvironment();
        ArrayList<String> list = new ArrayList<>();
        list.add("/common/defaultEngine.ftl");
        configuration.setAutoIncludes(list);
        HashMap<String, String> importMap = new HashMap<>(2);
//        importMap.put("web_macro", "/web_macro.ftl");
//        importMap.put("admin_macro", "/admin/admin_macro.ftl");
        configuration.setAutoImports(importMap);
        configuration.setSharedVariable("ctxStatic", new SimpleScalar(ctxPath));
        setSharedVariableFromAppProperty(env);
        try {
            configuration.setSharedVariable("appConfig", env);
            configuration.setSharedVariable("userAcl",
                    this.applicationContext.getBean(UserAccessControlService.class));
        } catch (TemplateModelException e) {
            log.warn("Couldn't set shared variable", e);
        }
        if (sharedVariableRegisters != null) {
            for (FreeMarkerSharedVariableRegisterAware sharedVariableRegister : sharedVariableRegisters) {
                sharedVariableRegister.getSharedVariables().forEach(configuration::setSharedVariable);
            }
        }
    }

    /*
     * 将application.properties中定义的属性值注入到FreeMarker页面作为公共变量
     */
    private void setSharedVariableFromAppProperty(Environment env) {
        // 定义配置条目二维数组，一维数组条目的三个元素分别是：application中的属性名，默认值，FreeMarker共享变量的值
        String[][] entries = {
                {"gunsmith.appVersion", "2.7.5", "appVersion"},
                {"gunsmith.appWebCacheBusting", "201908170915", "appWebCacheBusting"}};
        for (String[] entry : entries) {
            String str = env.getProperty(entry[0], entry[1]);
            configuration.setSharedVariable(entry[2], new SimpleScalar(str));
        }
    }
}
